package com.haixiaoke.saas.contract.service.impl;

import cn.hutool.core.bean.BeanUtil;
import cn.hutool.core.collection.CollectionUtil;
import cn.hutool.core.date.DateUtil;
import cn.hutool.core.util.ObjectUtil;
import cn.hutool.core.util.StrUtil;
import com.fasc.open.api.v5_1.req.signtask.AddFillFieldInfo;
import com.fasc.open.api.v5_1.res.template.FillActorFieldInfo;
import com.fasc.open.api.v5_1.res.template.SignTaskActorInfo;
import com.fasc.open.api.v5_1.res.template.SignTemplateDetailRes;
import com.haixiaoke.saas.bill.domain.HouseBill;
import com.haixiaoke.saas.bill.domain.HouseBillItemMerge;
import com.haixiaoke.saas.bill.service.IHouseBillItemMergeService;
import com.haixiaoke.saas.bill.service.IHouseBillService;
import com.haixiaoke.saas.common.constant.*;
import com.haixiaoke.saas.common.core.domain.AjaxResult;
import com.haixiaoke.saas.common.electronicVisa.domain.ElectronicVisaContract;
import com.haixiaoke.saas.common.enums.BillStateEnum;
import com.haixiaoke.saas.common.exception.ServiceException;
import com.haixiaoke.saas.common.utils.DateUtils;
import com.haixiaoke.saas.common.utils.PlaceholderUtil;
import com.haixiaoke.saas.contract.domain.ContractFacilitiesItem;
import com.haixiaoke.saas.contract.domain.ContractParameter;
import com.haixiaoke.saas.contract.domain.ContractTemplate;
import com.haixiaoke.saas.contract.domain.LesseeContract;
import com.haixiaoke.saas.contract.fadada.service.FaDaDaService;
import com.haixiaoke.saas.contract.mapper.LesseeContractMapper;
import com.haixiaoke.saas.contract.service.IContractFacilitiesItemService;
import com.haixiaoke.saas.contract.service.IContractTemplateService;
import com.haixiaoke.saas.contract.service.ILesseeContractService;
import com.haixiaoke.saas.contract.service.IProprietorService;
import com.haixiaoke.saas.department.domain.ElectronicVisa;
import com.haixiaoke.saas.department.domain.ElectronicVisaSignProgress;
import com.haixiaoke.saas.department.service.IElectronicVisaService;
import com.haixiaoke.saas.department.service.IElectronicVisaSignProgressService;
import com.haixiaoke.saas.house.domain.House;
import com.haixiaoke.saas.house.service.IHouseService;
import com.haixiaoke.saas.order.domain.Order;
import com.haixiaoke.saas.order.service.IOrderService;
import com.haixiaoke.saas.user.domain.UserConsumer;
import com.haixiaoke.saas.user.service.IUserConsumerService;
import org.apache.commons.lang3.RandomUtils;
import org.apache.commons.lang3.StringUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import java.math.BigDecimal;
import java.text.SimpleDateFormat;
import java.util.ArrayList;
import java.util.Date;
import java.util.List;
import java.util.Map;
import java.util.stream.Collectors;

/**
 * 租客合同Service业务层处理
 *
 * @author panda
 * @date 2024-06-04
 */
@Service
public class LesseeContractServiceImpl implements ILesseeContractService {
    @Autowired
    private LesseeContractMapper lesseeContractMapper;
    @Autowired
    private IOrderService orderService;
    @Autowired
    private IHouseService houseService;
    @Autowired
    private IElectronicVisaService electronicVisaService;
    @Autowired
    private IContractTemplateService contractTemplateService;
    @Autowired
    private IContractFacilitiesItemService contractFacilitiesItemService;
    @Autowired
    private IUserConsumerService userConsumerService;
    @Autowired
    private IElectronicVisaSignProgressService electronicVisaSignProgressService;
    @Autowired
    private FaDaDaService faDaDaService;

    @Autowired
    private IHouseBillItemMergeService houseBillItemMergeService;
    @Autowired
    private IHouseBillService houseBillService;
    @Autowired
    private IProprietorService proprietorService;

    /**
     * 查询租客合同
     *
     * @param lesseeContractId 租客合同主键
     * @return 租客合同
     */
    @Override
    public LesseeContract selectLesseeContractByLesseeContractId(String lesseeContractId) {
        LesseeContract lesseeContract = lesseeContractMapper.selectLesseeContractByLesseeContractId(lesseeContractId);
        Order order = orderService.selectOrderById(lesseeContract.getOrderId());
        lesseeContract.setOrder(order);
        List<ContractFacilitiesItem> contractFacilitiesItemList = contractFacilitiesItemService.selectContractFacilitiesItemByContractId(lesseeContractId);
        lesseeContract.setContractFacilitiesItemList(contractFacilitiesItemList);
        return lesseeContract;
    }

    @Override
    public LesseeContract selectLesseeContractById(String lesseeContractId) {
        return lesseeContractMapper.selectLesseeContractByLesseeContractId(lesseeContractId);
    }

    /**
     * 查询租客合同列表
     *
     * @param lesseeContract 租客合同
     * @return 租客合同
     */
    @Override
    public List<LesseeContract> selectLesseeContractList(LesseeContract lesseeContract) {
        return lesseeContractMapper.selectLesseeContractList(lesseeContract);
    }

    /**
     * 新增租客合同
     *
     * @param lesseeContract 租客合同
     * @return 结果
     */
    @Override
    @Transactional
    public int insertLesseeContract(LesseeContract lesseeContract) {
        Date nowDate = DateUtils.getNowDate();
        UserConsumer userConsumer = userConsumerService.selectUserConsumerByMobile(lesseeContract.getContactPhone());
        if (ObjectUtil.isEmpty(userConsumer)) {
            userConsumer = new UserConsumer();
            userConsumer.setUserMobile(lesseeContract.getContactPhone());
            userConsumer.setUserName(lesseeContract.getContactName());
            userConsumer.setCardNumber(lesseeContract.getCardNumber());
            userConsumer.setLesseeFlag(UserConstants.LESSEE_FLAG_YES);
            userConsumer.setCreateBy(lesseeContract.getCreateBy());
            userConsumerService.insertUserConsumer(userConsumer);
        } else {
            userConsumer.setLesseeFlag(UserConstants.LESSEE_FLAG_YES);
            userConsumer.setUserName(lesseeContract.getContactName());
            userConsumer.setCardNumber(lesseeContract.getCardNumber());
            userConsumer.setUpdateTime(nowDate);
            userConsumer.setUpdateBy(lesseeContract.getCreateBy());
            userConsumerService.updateUserConsumer(userConsumer);
        }
        List<ElectronicVisaSignProgress> signProgressList = new ArrayList<>();

        // 封装订单预订人信息
        lesseeContract.getOrder().setReserveUser(lesseeContract.getContactName());
        lesseeContract.getOrder().setReserveUserPhone(lesseeContract.getContactPhone());
        lesseeContract.getOrder().setReserveUserId(userConsumer.getUserId());
        lesseeContract.setConUserId(userConsumer.getUserId());
        // 新增订单
        Order order;
        if (StrUtil.isBlank(lesseeContract.getOrder().getOrderId())) {
            order = orderService.insertPreOrder(lesseeContract.getOrder());
        } else {
            int orderResult = orderService.updateOrder(lesseeContract.getOrder());
            if (orderResult == 0) {
                throw new ServiceException("订单更新失败");
            }
            order = orderService.selectOrderById(lesseeContract.getOrder().getOrderId());
        }
        if (ObjectUtil.isEmpty(order)) {
            throw new ServiceException("订单生成失败");
        }

        // 查询房屋数据
        House house = houseService.selectHouseInfoByHouseId(lesseeContract.getHouseId());

        ElectronicVisa electronicVisa = null;

        // 封装合同内容数据
        if (ContractConstants.CONTRACT_TYPE_ELECTRONIC.equals(lesseeContract.getContractType())) {
            // 查询电子签数据
            boolean partyType = false;
            if (HouseConstants.COOPERATION_TYPE_AGENCY_SERVICE.equals(house.getCooperationType())) {
                // 房屋委托
                electronicVisa = electronicVisaService.selectElectronicVisaByProprietorUserId(house.getProprietorUserId());
                if (ObjectUtil.isNotNull(electronicVisa) &&
                        TenantConstants.ELECTRONIC_VISA_TYPE_PERSON.equals(electronicVisa.getElectronicVisaType())) {
                    partyType = true;
                }
            } else if (HouseConstants.COOPERATION_TYPE_HOUSE_RENTAL.equals(house.getCooperationType())) {
                // 代理服务
                electronicVisa = electronicVisaService.selectElectronicVisaByTenantId(lesseeContract.getTenantId());
            }
            if (ObjectUtil.isNull(electronicVisa)) {
                throw new ServiceException("电子签证信息不存在");
            }

            // 封装签署任务数据
            ElectronicVisaSignProgress lesseeSignProgress = new ElectronicVisaSignProgress();
            if (ContractConstants.LESSEE_TYPE_PERSON.equals(lesseeContract.getLesseeType())) {
                lesseeSignProgress.setSigner(lesseeContract.getContactName());
            } else if (ContractConstants.LESSEE_TYPE_ENTERPRISE.equals(lesseeContract.getLesseeType())) {
                lesseeSignProgress.setSigner(lesseeContract.getEnterpriseName());
            }
            lesseeSignProgress.setSignType(TenantConstants.SIGN_TYPE_PARTY_B);
            ElectronicVisaSignProgress initiatorSignProgress = new ElectronicVisaSignProgress();
            initiatorSignProgress.setSigner(electronicVisa.getOrganizationName());
            initiatorSignProgress.setSignType(TenantConstants.SIGN_TYPE_PARTY_A);
            signProgressList.add(lesseeSignProgress);
            signProgressList.add(initiatorSignProgress);

            // 电子签
            SignTemplateDetailRes signTemplateDetail = faDaDaService.getSignTemplateDetail(lesseeContract.getContractTemplateId());
            List<AddFillFieldInfo> list = new ArrayList<>();
            List<SignTaskActorInfo> actors = signTemplateDetail.getActors();
            for (SignTaskActorInfo actor : actors) {
                // ActorInfo actorInfo = actor.getActorInfo();
                // Boolean initiator = actorInfo.getInitiator();
                // if (initiator) {
                // }
                List<FillActorFieldInfo> fillFields = actor.getFillFields();
                if (CollectionUtil.isNotEmpty(fillFields)) {
                    for (FillActorFieldInfo fillField : fillFields) {
                        AddFillFieldInfo info = new AddFillFieldInfo();
                        info.setFieldDocId(fillField.getFieldDocId().toString());
                        info.setFieldValue(buildValue(fillField.getFieldId(), lesseeContract, order, house, electronicVisa));
                        info.setFieldId(fillField.getFieldId());
                        info.setFieldName(faDaDaService.buildFieldName(fillField.getFieldId()));
                        list.add(info);
                    }
                }
            }
            ElectronicVisaContract electronicVisaContract = buildElectronicVisaContract(list, lesseeContract, order, house, electronicVisa, partyType);
            // 签署任务id
            String signTaskId = faDaDaService.createWithTemplate(electronicVisaContract);
            lesseeContract.setFlowId(signTaskId);
        } else {
            ContractTemplate contractTemplate = contractTemplateService.selectContractTemplateByContractTemplateId(lesseeContract.getContractTemplateId());
            if (ObjectUtil.isEmpty(contractTemplate)) {
                throw new ServiceException("合同模板不存在");
            }
            if (ContractConstants.TEMPLATE_STATE_CONCEAL.equals(contractTemplate.getTemplateState())) {
                throw new ServiceException("合同模板已被隐藏");
            }
            // 判断合同类型和合同模板类型是否匹配
            if (!((ContractConstants.TEMPLATE_TYPE_PERSONAL_PAPER.equals(contractTemplate.getTemplateType()) &&
                    ContractConstants.CONTRACT_TYPE_PERSONAL_PAPER.equals(lesseeContract.getContractType()))
                    || (ContractConstants.TEMPLATE_TYPE_ENTERPRISE_PAPER.equals(contractTemplate.getTemplateType()) &&
                    ContractConstants.CONTRACT_TYPE_ENTERPRISE_PAPER.equals(lesseeContract.getContractType())))) {
                throw new ServiceException("合同类型和合同模板类型不匹配");
            }
            // 创建合同具体数据
            Map<String, Object> map = buildContractParameter(lesseeContract, order, house, lesseeContract.getContractFacilitiesItemList());

            String content = PlaceholderUtil.format(contractTemplate.getTemplateContent(), map, "");
            if (StrUtil.isBlank(content)) {
                throw new ServiceException("合同内容生成错误");
            }

            // 封装纸质合同内容数据
            lesseeContract.setTemplateContent(contractTemplate.getTemplateContent());
            lesseeContract.setContractContent(content);
        }

        // 生成组合合同内容数据
        String lesseeContractId = "LC" + System.currentTimeMillis() + RandomUtils.nextInt(10000, 100000);
        lesseeContract.setLesseeContractId(lesseeContractId);
        lesseeContract.setOrderId(order.getOrderId());
        lesseeContract.setCreateTime(nowDate);
        lesseeContract.setProprietorUserId(house.getProprietorUserId());
        lesseeContract.setContractScanning(StringUtils.join(lesseeContract.getContractScanningList(), ","));
        if (ContractConstants.SIGNING_MODE_PLATFORM.equals(lesseeContract.getSigningMode())) {
            lesseeContract.setLesseeContractStatus(ContractConstants.LESSEE_CONTRACT_STATUS_BE_SIGNING);
        } else if (ContractConstants.SIGNING_MODE_PROPRIETOR.equals(lesseeContract.getSigningMode())) {
            lesseeContract.setLesseeContractStatus(ContractConstants.LESSEE_CONTRACT_STATUS_UNCONFIRMED);
        }
        int result = lesseeContractMapper.insertLesseeContract(lesseeContract);
        if (result > 0) {
            // 插入房屋设施数据集合
            List<ContractFacilitiesItem> contractFacilitiesItemList = lesseeContract.getContractFacilitiesItemList();
            if (CollectionUtil.isNotEmpty(contractFacilitiesItemList)) {
                contractFacilitiesItemList.forEach(item -> {
                    item.setLesseeContractId(lesseeContract.getLesseeContractId());
                    item.setOrderId(order.getOrderId());
                    item.setHouseId(lesseeContract.getHouseId());
                    item.setCreateTime(nowDate);
                    item.setCreateBy(lesseeContract.getCreateBy());
                });
                contractFacilitiesItemService.insertBatchFacilitiesItem(contractFacilitiesItemList);
            }
            // 插入签署进度
            if (signProgressList.size() == 2) {
                signProgressList.forEach(progress -> {
                    progress.setContractId(lesseeContract.getLesseeContractId());
                    progress.setSignProgress(TenantConstants.SIGN_PROGRESS_UNSIGNED);
                    progress.setContractType(TenantConstants.CONTRACT_TYPE_LESSEE);
                    progress.setCreateTime(nowDate);
                    progress.setCreateBy(lesseeContract.getCreateBy());
                    progress.setTenantId(lesseeContract.getTenantId());
                });
                electronicVisaSignProgressService.insertBatchElectronicVisaSignProgress(signProgressList);
            }

            if (ObjectUtil.isNotEmpty(electronicVisa)) {
                // 更新电子签状态
                electronicVisaService.subtractVisaContractNumber(electronicVisa.getVisaId());
            }
        }

        // 提交账单
        List<HouseBill> houseBillList = lesseeContract.getHouseBillList();
        if (CollectionUtil.isEmpty(houseBillList)) {
            return result;
        }
        List<HouseBillItemMerge> list = new ArrayList<>();
        for (HouseBill houseBill : houseBillList) {
            houseBill.setOrderId(order.getOrderId());
            houseBill.setLesseeContractId(lesseeContract.getLesseeContractId());
            List<HouseBillItemMerge> houseBillItemMerges = houseBill.getHouseBillItemMerges();
            BigDecimal reduce = houseBillItemMerges.stream().map(HouseBillItemMerge::getItemPrice)
                    .reduce(BigDecimal.ZERO, BigDecimal::add);
            houseBill.setCost(reduce);
            houseBill.setPenaltyStates(lesseeContract.getPenaltyStates());
            houseBill.setPenaltyScale(lesseeContract.getPenaltyScale());
            if (houseBill.getBillCreateTime() == null) {
                houseBill.setBillCreateTime(DateUtils.getNowDate());
            }
            houseBill.setUserId(userConsumer.getUserId());
            houseBill.setUserName(StrUtil.isEmpty(userConsumer.getUserName()) ? userConsumer.getNickName() : userConsumer.getUserName());
            houseBill.setCreateBy(lesseeContract.getCreateBy());
            houseBill.setCreateTime(DateUtils.getNowDate());
            list.addAll(houseBillItemMerges);
        }
        houseBillService.batchInsert(houseBillList);
        houseBillItemMergeService.batchInsertHouseBillItemMerges(list);

        return result;
    }

    /**
     * @param list           合同组件信息
     * @param lesseeContract 租客合同内容
     * @param order          订单内容
     * @param house          房屋信息
     * @param electronicVisa 电子签信息
     * @param partyType      合同签署类型:true:个人签署，false:机构签署
     * @return
     */
    private ElectronicVisaContract buildElectronicVisaContract(List<AddFillFieldInfo> list,
                                                               LesseeContract lesseeContract, Order order, House house,
                                                               ElectronicVisa electronicVisa, Boolean partyType) {
        ElectronicVisaContract electronicVisaContract = new ElectronicVisaContract();
        electronicVisaContract.setTemplateId(lesseeContract.getContractTemplateId());
        electronicVisaContract.setName(lesseeContract.getContactName());
        electronicVisaContract.setMobile(lesseeContract.getContactPhone());
        electronicVisaContract.setIdCard(lesseeContract.getCardNumber());
        electronicVisaContract.setActorCorporateName(lesseeContract.getEnterpriseName());
        electronicVisaContract.setActorSocialCreditCode(lesseeContract.getSocialCreditCode());
        electronicVisaContract.setFillFieldList(list);
        electronicVisaContract.setOpenId(electronicVisa.getOpenId());
        electronicVisaContract.setProxyOperatorOpenid(electronicVisa.getProxyOperatorOpenid());
        electronicVisaContract.setActorName(electronicVisa.getOrganizationName());
        electronicVisaContract.setExpiresTime(lesseeContract.getLatestSigningTime());
        electronicVisaContract.setPartyType(partyType);
        electronicVisaContract.setActorPartyType(!ContractConstants.CONTRACT_TYPE_ENTERPRISE_PAPER.equals(lesseeContract.getContractType()));
        return electronicVisaContract;
    }

    /**
     * 封装电子合同参数
     *
     * @param fieldId
     * @return
     */
    public String buildValue(String fieldId, LesseeContract lesseeContract, Order order, House house, ElectronicVisa electronicVisa) {
        String fieldValue = "";
        switch (fieldId) {
            case TencentContractTemplateModule.HOUSE_ADDRESS:
                fieldValue = order.getPremisesAddress();
                break;
            case TencentContractTemplateModule.ORG_NAME:
                fieldValue = electronicVisa.getOrganizationName();
                break;
            case TencentContractTemplateModule.USCC:
                if (StrUtil.equals(TenantConstants.ELECTRONIC_VISA_TYPE_ENTERPRISE,electronicVisa.getElectronicVisaType())) {
                    fieldValue = electronicVisa.getSocialCreditCode();
                }
                break;
            case TencentContractTemplateModule.PARTY_A_CARD:
                if (StrUtil.equals(TenantConstants.ELECTRONIC_VISA_TYPE_PERSON,electronicVisa.getElectronicVisaType())) {
                    fieldValue = electronicVisa.getCardNumber();
                }
                break;
            case TencentContractTemplateModule.HOUSE_TYPE:
                String houseType = "";
                String room = house.getRoomType();
                String hall = house.getHall();
                String toilet = house.getToilet();
                if (StrUtil.isNotBlank(room)) {
                    houseType += room + "室";
                }
                if (StrUtil.isNotBlank(hall)) {
                    houseType += hall + "厅";
                }
                if (StrUtil.isNotBlank(toilet)) {
                    houseType += toilet + "卫";
                }
                fieldValue = houseType;
                break;
            case TencentContractTemplateModule.AREA:
                fieldValue = house.getHouseArea() + "m²";
                break;
            case TencentContractTemplateModule.USER_NAME:
                fieldValue = lesseeContract.getContactName();
                break;
            case TencentContractTemplateModule.ID_CARD:
                fieldValue = lesseeContract.getCardNumber();
                break;
            case TencentContractTemplateModule.LEASE_START_TIME:
                fieldValue = DateUtil.format(order.getCheckInTime(), "yyyy-MM-dd");
                break;
            case TencentContractTemplateModule.LEASE_END_TIME:
                fieldValue = DateUtil.format(order.getCheckOutTime(), "yyyy-MM-dd");
                break;
            case TencentContractTemplateModule.RENT:
                if (OrderConstants.RENTAL_MODE_MONTH.equals(order.getRentalMode())) {
                    fieldValue = order.getMonthRent().toString();
                } else if (OrderConstants.RENTAL_MODE_DISPOSABLE.equals(order.getRentalMode())) {
                    fieldValue = order.getTotalRent().toString();
                }
                break;
            case TencentContractTemplateModule.CASH_PLEDGE:
                if (OrderConstants.RENTAL_MODE_MONTH.equals(order.getRentalMode())) {
                    // 押金金额 = 月租金 * 押几数量
                    fieldValue = order.getMonthRent().multiply(BigDecimal.valueOf(order.getDepositNumber())).toString();
                } else if (OrderConstants.RENTAL_MODE_DISPOSABLE.equals(order.getRentalMode())) {
                    fieldValue = order.getDeposit().toString();
                }
                break;
            case TencentContractTemplateModule.PAYMENT_DATE:
                if (OrderConstants.RENTAL_MODE_MONTH.equals(order.getRentalMode())) {
                    if (OrderConstants.RENT_DAY_TYPE_DAY.equals(order.getRentDayType())) {
                        fieldValue = "每期提前" + order.getRentCollectionDate() + "天收租";
                    } else if (OrderConstants.RENT_DAY_TYPE_FIRST_MONTH.equals(order.getRentDayType())) {
                        fieldValue = "每期第一个月" + order.getRentCollectionDate() + "号收租";
                    } else if (OrderConstants.RENT_DAY_TYPE_PRE_MONTH.equals(order.getRentDayType())) {
                        fieldValue = "每期提前一个月" + order.getRentCollectionDate() + "号收租";
                    }
                } else if (OrderConstants.RENTAL_MODE_DISPOSABLE.equals(order.getRentalMode())) {
                    fieldValue = DateUtil.format(DateUtils.getNowDate(), "yyyy-MM-dd");
                }
                break;
            case TencentContractTemplateModule.DELIVERY_PERIOD:
                fieldValue = DateUtil.format(order.getCheckInTime(), "yyyy-MM-dd");
                break;
            case TencentContractTemplateModule.ADDITIONAL_TERMS:
                if (StrUtil.isNotBlank(lesseeContract.getSupplementaryTerms())) {
                    fieldValue = lesseeContract.getSupplementaryTerms();
                } else {
                    fieldValue = "无";
                }
                break;
            default:
                break;
        }
        return fieldValue;
    }

    /**
     * 封装纸质合同参数
     *
     * @param lesseeContract             租客合同
     * @param order                      订单
     * @param house                      房屋
     * @param contractFacilitiesItemList 房屋设施列表
     * @return
     */
    private Map<String, Object> buildContractParameter(LesseeContract lesseeContract, Order order, House house, List<ContractFacilitiesItem> contractFacilitiesItemList) {
        SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd");

        ContractParameter parameter = new ContractParameter();
        // 合同编号
        parameter.setContractId(StrUtil.isBlank(lesseeContract.getContractNumber()) ? "" : lesseeContract.getContractNumber());
        // 城市
        parameter.setCity(order.getCityName());
        // 房屋地址(楼盘+楼栋+单元+门牌号)
        parameter.setHouseAddress(order.getPremisesAddress());
        // 户型(几室几厅几卫)
        parameter.setHouseType(house.getHouseType() + "室" + house.getHall() + "厅" + house.getToilet() + "卫");
        // 楼层
        parameter.setFloor(String.valueOf(house.getFloors()));
        // 总楼层
        parameter.setTotalFloor(String.valueOf(house.getUnit().getFloors()));
        // 房屋面积
        parameter.setHouseArea(house.getHouseArea() + "m²");
        // 租住起始日期
        parameter.setStartDate(sdf.format(order.getCheckInTime()));
        // 租住结束日期
        parameter.setEndDate(sdf.format(order.getCheckOutTime()));
        // 补充条款
        parameter.setAdditionalTerms(lesseeContract.getSupplementaryTerms());
        // 签约人
        parameter.setSigner(lesseeContract.getSigner());
        // 签约日期
        parameter.setSignDate(sdf.format(lesseeContract.getSigningTime()));
        // 房屋设施
        if (CollectionUtil.isNotEmpty(contractFacilitiesItemList)) {
            StringBuilder table = new StringBuilder();
            table.append(String.format("%-10s", "|    设施名称   "));
            table.append(String.format("%-10s", "|    数量   "));
            table.append(String.format("%-10s", "|    价格(元)   |"));
            table.append("\n");
            table.append(String.format("%-10s", "|-------------|----------|---------|"));
            for (ContractFacilitiesItem item : contractFacilitiesItemList) {
                table.append(String.format("%-10s", "|    " + item.getFacilitiesName() + "   "));
                table.append(String.format("%-10s", "|    " + item.getFacilitiesNumber() + "   "));
                table.append(String.format("%-10s", "|    " + item.getFacilitiesPrice() + "   |"));
                table.append("\n");
            }
            parameter.setHouseFacilities(table.toString());
        } else {
            parameter.setHouseFacilities("");
        }
        // 电表读数
        parameter.setElectricityMeterReading(String.valueOf(lesseeContract.getElectricityMeterReading()));
        // 水表读数
        parameter.setWaterMeterReading(String.valueOf(lesseeContract.getWaterMeterReading()));
        String payType = "";
        // 房费金额
        BigDecimal rentAmount = BigDecimal.ZERO;
        if (OrderConstants.RENTAL_MODE_MONTH.equals(order.getRentalMode())) {
            payType = "月付";
            rentAmount = order.getMonthRent();
            // 押付方式
            parameter.setPaymentMethod("押" + order.getDepositNumber() + "付" + order.getPayNumber());
            // 收租日
            String rentDay = "";
            if (OrderConstants.RENT_DAY_TYPE_DAY.equals(order.getRentDayType())) {
                rentDay = "每期提前" + order.getRentCollectionDate() + "天收租";
            } else if (OrderConstants.RENT_DAY_TYPE_FIRST_MONTH.equals(order.getRentDayType())) {
                rentDay = "每期第一个月" + order.getRentCollectionDate() + "号收租";
            } else if (OrderConstants.RENT_DAY_TYPE_PRE_MONTH.equals(order.getRentDayType())) {
                rentDay = "每期提前一个月" + order.getRentCollectionDate() + "号收租";
            }
            parameter.setRentDay(rentDay);
        } else if (OrderConstants.RENTAL_MODE_DISPOSABLE.equals(order.getRentalMode())) {
            payType = "一次性";
            rentAmount = order.getTotalRent();
            // 押金金额
            parameter.setDepositAmount(String.valueOf(order.getDeposit()));
        }
        parameter.setRentAmount(String.valueOf(rentAmount));
        // 付款方式
        parameter.setPayType(payType);
        if (ContractConstants.LESSEE_TYPE_PERSON.equals(lesseeContract.getLesseeType())) {
            // 承租人姓名
            parameter.setTenantName(lesseeContract.getContactName());
            // 承租人手机号
            parameter.setTenantPhone(lesseeContract.getContactPhone());
            // 承租人身份证号码
            parameter.setTenantIdCard(lesseeContract.getCardNumber());
        } else if (ContractConstants.LESSEE_TYPE_ENTERPRISE.equals(lesseeContract.getLesseeType())) {
            // 公司名称
            parameter.setCompanyName(lesseeContract.getEnterpriseName());
            // 统一社会信用代码
            parameter.setCreditCode(lesseeContract.getSocialCreditCode());
            // 企业联系人
            parameter.setContactPerson(lesseeContract.getContactName());
            // 联系人手机号
            parameter.setContactPhone(lesseeContract.getContactPhone());
        }
        // 生成纸质合同内容数据
        return BeanUtil.beanToMap(parameter);
    }

    /**
     * 修改租客合同
     *
     * @param lesseeContract 租客合同
     * @return 结果
     */
    @Override
    public int updateLesseeContract(LesseeContract lesseeContract) {
        lesseeContract.setUpdateTime(DateUtils.getNowDate());
        return lesseeContractMapper.updateLesseeContract(lesseeContract);
    }

    /**
     * 批量删除租客合同
     *
     * @param lesseeContractIds 需要删除的租客合同主键
     * @return 结果
     */
    @Override
    public int deleteLesseeContractByLesseeContractIds(String[] lesseeContractIds) {
        return lesseeContractMapper.deleteLesseeContractByLesseeContractIds(lesseeContractIds);
    }

    /**
     * 删除租客合同信息
     *
     * @param lesseeContractId 租客合同主键
     * @return 结果
     */
    @Override
    public int deleteLesseeContractByLesseeContractId(String lesseeContractId) {
        return lesseeContractMapper.deleteLesseeContractByLesseeContractId(lesseeContractId);
    }

    @Override
    public List<LesseeContract> flatSelectLesseeContractList(LesseeContract lesseeContract) {
        return lesseeContractMapper.flatSelectLesseeContractList(lesseeContract);
    }

    @Override
    public String selectLesseeContractElectronicVisaPreviewUrl(LesseeContract lesseeContract) {
        LesseeContract contract = lesseeContractMapper.selectLesseeContractByLesseeContractId(lesseeContract.getLesseeContractId());
        if (ObjectUtil.isNotEmpty(contract) && ContractConstants.CONTRACT_TYPE_ELECTRONIC.equals(contract.getContractType())) {
            return faDaDaService.getSignTaskPreviewUrl(contract.getFlowId(), lesseeContract.getRedirectUrl());
        }
        return null;
    }

    /**
     * 上传合同图片
     *
     * @param lesseeContract
     * @return
     */
    @Override
    public AjaxResult uploadContractImage(LesseeContract lesseeContract) {
        if (CollectionUtil.isEmpty(lesseeContract.getContractImageList())) {
            return AjaxResult.error("请上传合同图片");
        }
        LesseeContract contract = lesseeContractMapper.selectLesseeContractByLesseeContractId(lesseeContract.getLesseeContractId());

        if (ObjectUtil.isNotEmpty(contract)) {


            // 签署完成 更新关联账单
            houseBillService.updateBillEnableStates(contract.getLesseeContractId(), BillStateEnum.BILL_ENABLE_STATES_ON.getValue());
            houseBillService.houseBillActivationTask();

            if (ContractConstants.CONTRACT_TYPE_ELECTRONIC.equals(contract.getContractType())) {
                return AjaxResult.error("电子合同不支持上传图片");
            }
            if (lesseeContract.getContractImageList().size() > 30) {
                return AjaxResult.error("合同图片不能超过30张");
            }
            lesseeContract.setContractImage(StringUtils.join(lesseeContract.getContractImageList(), ","));
            lesseeContract.setLesseeContractStatus(ContractConstants.LESSEE_CONTRACT_STATUS_SIGN_OFF);
            lesseeContract.setUpdateTime(DateUtils.getNowDate());
            return lesseeContractMapper.updateLesseeContract(lesseeContract) > 0 ? AjaxResult.success() : AjaxResult.error();
        }
        return AjaxResult.error("合同不存在");
    }

    @Override
    public int repealLesseeContract(LesseeContract lesseeContract) {
        // 电子合同,且状态为待确认，则更新电子签数量
        if (ContractConstants.LESSEE_CONTRACT_STATUS_UNCONFIRMED.equals(lesseeContract.getLesseeContractStatus())
                && ContractConstants.CONTRACT_TYPE_ELECTRONIC.equals(lesseeContract.getContractType())) {
            House house = houseService.selectHouseById(lesseeContract.getHouseId());
            ElectronicVisa electronicVisa = electronicVisaService.selectElectronicVisaByCooperationType(house);
            electronicVisaService.addVisaContractNumber(electronicVisa.getVisaId());
        }

        if (ContractConstants.CONTRACT_TYPE_ELECTRONIC.equals(lesseeContract.getContractType())) {
            // 电子合同，调用撤销接口取消合同
            faDaDaService.cancel(lesseeContract.getFlowId());
        } else if (ContractConstants.CONTRACT_TYPE_PERSONAL_PAPER.equals(lesseeContract.getContractType()) ||
                ContractConstants.CONTRACT_TYPE_ENTERPRISE_PAPER.equals(lesseeContract.getContractType())) {
            // 纸质合同，直接更新状态为终止
            lesseeContract.setLesseeContractStatus(ContractConstants.LESSEE_CONTRACT_STATUS_TERMINATED);
            lesseeContract.setUpdateTime(DateUtils.getNowDate());
        }
        return lesseeContractMapper.updateLesseeContract(lesseeContract);
    }

    @Override
    public int repealLesseeContractByOrderId(String orderId) {
        List<LesseeContract> lesseeContracts = lesseeContractMapper.selectInvalidLesseeContractByOrderId(orderId);
        int result = 0;
        if (CollectionUtil.isNotEmpty(lesseeContracts)) {
            for (LesseeContract contract : lesseeContracts) {
                result += this.repealLesseeContract(contract);
            }
        }
        return result;
    }

    @Override
    public boolean checkRelaunch(String orderId) {
        return lesseeContractMapper.checkRelaunch(orderId) > 0;
    }

    @Override
    public AjaxResult signingLesseeContract(LesseeContract lesseeContract, Boolean participantType, Long conUserId) {
        LesseeContract contract = lesseeContractMapper.selectLesseeContractByLesseeContractId(lesseeContract.getLesseeContractId());

        if (ObjectUtil.isNotEmpty(contract)) {

            if (participantType && StrUtil.equals(ContractConstants.UN_SIGNED_FLAG, contract.getPartyASignFlag())) {
                return AjaxResult.error("甲方未签署,不能先签署");
            }

            if (ContractConstants.SIGNING_MODE_PLATFORM.equals(contract.getSigningMode())
                    && !participantType && ObjectUtil.isNotEmpty(conUserId)) {
                return AjaxResult.error("平台为签署方,不需要业主签署");
            }

            if (ContractConstants.SIGNING_MODE_PROPRIETOR.equals(contract.getSigningMode())
                    && !participantType && ObjectUtil.isEmpty(conUserId)) {
                return AjaxResult.error("业主为签署方,不需要平台签署");
            }

            if (!ContractConstants.CONTRACT_TYPE_ELECTRONIC.equals(contract.getContractType())) {
                return AjaxResult.warn("纸质合同不支持签约");
            }
            if (!ContractConstants.LESSEE_CONTRACT_STATUS_BE_SIGNING.equals(contract.getLesseeContractStatus())) {
                return AjaxResult.warn("合同状态异常，请刷新后再试");
            }
            if (StrUtil.isBlank(contract.getFlowId())) {
                return AjaxResult.warn("该合同数据错误，无法签约");
            }
            if (ObjectUtil.isNotEmpty(conUserId)) {
                if (participantType) {
                    // 乙方
                    if (!contract.getConUserId().equals(conUserId)) {
                        return AjaxResult.error("非法操作");
                    }
                } else {
                    // 甲方
                    if (conUserId != null) {
                        if (!contract.getProprietorUserId().equals(conUserId)) {
                            return AjaxResult.error("非法操作");
                        }
                    } else {
                        if (!lesseeContract.getTenantId().equals(contract.getTenantId())) {
                            return AjaxResult.error("非法操作");
                        }
                    }
                }
            }

            String actorUrl = faDaDaService.getActorUrl(contract.getFlowId(), lesseeContract.getRedirectUrl(), participantType);
            return StrUtil.isBlank(actorUrl) ? AjaxResult.error("数据异常，请联系管理员") : AjaxResult.success("操作成功", actorUrl);
        }
        return AjaxResult.error();
    }

    @Override
    public int frontDeletedLesseeContract(String lesseeContractId) {
        return lesseeContractMapper.frontDeletedLesseeContract(lesseeContractId);
    }

    @Override
    public LesseeContract selectLesseeContractByFlowId(String flowId) {
        return lesseeContractMapper.selectLesseeContractByFlowId(flowId);
    }

    @Override
    public void lesseeContractOverdueTask() {
        List<LesseeContract> contractList = lesseeContractMapper.selectLesseeContractOverdueTask();
        if (CollectionUtil.isNotEmpty(contractList)) {

            List<String> ids = contractList.stream()
                    .map(LesseeContract::getLesseeContractId).collect(Collectors.toList());
            lesseeContractMapper.updateBatchLesseeContractByStatus(ids, ContractConstants.LESSEE_CONTRACT_STATUS_OVERDUE);
        }
    }

    @Override
    public LesseeContract selectLesseeContractByOrderId(String orderId) {
        return lesseeContractMapper.selectLesseeContractByOrderId(orderId);
    }
}
